
import 'dart:convert';

import 'package:xim/common/module/webview.dart';
import 'package:xim/config/route_config.dart';
import 'package:xim/router/index.dart';

/// 二维码内置数据
abstract class IQrResult<T>{

  QrResultCode get code;

  T Function() get action;

  Map<String, dynamic> parameters = {};

  Map<String,dynamic> toJson();

  String buildQr()=> json.encode(this);

  static IQrResult parse(String qrResult){
    try {
      var qrDecodeMap = json.decode(qrResult);
      var code = qrDecodeMap['code'];
      var qrResultCode = QrResultCode.valueOf(code);
      return qrResultCode.getHandler(qrDecodeMap);
    } catch(e){
      // 不是自己系统自己的QR
      if(qrResult.toLowerCase().startsWith("http")){
        var uri = Uri.tryParse(qrResult);
        if(uri !=null){
          return HttpWebQrResult(Uri.parse(qrResult));
        }
      }
      return TextQrResult(qrResult);
    }
  }
}

/// 页面跳转
class PageRouteQrResult extends IQrResult<void> {
  final PageRouteType routeType;
  final String path;
  PageRouteQrResult(this.path, {this.routeType=PageRouteType.replace});

  PageRouteQrResult.fromJson(Map<String, dynamic> jsonMap):
        routeType = jsonMap['routeType']!=null
            ? PageRouteType.tryParse(jsonMap['routeType'])?? PageRouteType.replace
            : PageRouteType.replace,
        path = jsonMap['path']
  ;

  @override
  void Function() get action =>(){
    routeType.go(path);
  };

  @override
  QrResultCode get code => QrResultCode.route;

  @override
  Map<String, dynamic> toJson() =>{
    "code": code.code,
    "path": path,
    "routeType": routeType.type,
  };

}

/// Web页面
class HttpWebQrResult extends IQrResult<void> {

  final Uri path;

  final PageRouteType routeType;

  /// true using InAppBrowser else InAppWebView
  final bool isBrowser;

  HttpWebQrResult(this.path, {this.routeType=PageRouteType.replace, this.isBrowser=false});

  HttpWebQrResult.fromJson(Map<String, dynamic> jsonMap):
        path= Uri.tryParse(jsonMap['path'])??Uri.parse(jsonMap['https://cn.bing.com/search?q=${jsonMap['path']}']),
        routeType = jsonMap['routeType']!=null
            ? PageRouteType.tryParse(jsonMap['routeType'])?? PageRouteType.replace
            : PageRouteType.replace,
        isBrowser = jsonMap['isBrowser'] ?? false
  ;

  @override
  void Function() get action => ()=> {
    if(isBrowser){
      WebViewUtil.openBrowser(path)
    }else{
      Routers.toWebViewPage(path.toString())
    }
  };

  @override
  QrResultCode get code => QrResultCode.web;

  @override
  Map<String, dynamic> toJson() =>{
    "code": code.code,
    "path": path,
    "isBrowser": isBrowser,
    "routeType": routeType.type
  };
}

/// 文本数据结果
class TextQrResult extends  IQrResult<void> {

  final String content;

  final PageRouteType routeType;

  TextQrResult(this.content, {this.routeType=PageRouteType.replace});

  @override
  void Function() get action => ()=> Routers.toWebViewPage(content);

  @override
  QrResultCode get code => QrResultCode.text;

  @override
  Map<String, dynamic> toJson() =>{
    "code": code.code,
    "content": content,
    "routeType": routeType.type,
  };

  TextQrResult.fromJson(Map<String, dynamic> jsonMap):
      routeType = jsonMap['routeType']!=null
          ? PageRouteType.tryParse(jsonMap['routeType'])?? PageRouteType.replace
          : PageRouteType.replace,
      content = jsonMap['content']??'';

}

/// 页面跳转方式
enum PageRouteType {

  push(1),

  replace(2),
  ;

  final int type;

  const PageRouteType(this.type);

  void go(String path, {Object? extra}){
    switch (this) {
      case PageRouteType.push:
        router.push(path, extra: extra);
        break;
      case PageRouteType.replace:
        router.replace(path, extra: extra);
        break;
      default: {
      }
    }
  }
  static PageRouteType? tryParse(int? code){
    if(code == null) {
      return null;
    }
    for(var it in PageRouteType.values){
      if(it.type == code){
        return it;
      }
    }
    return null;
  }
}

/// 二维码行为代码(唯一对应一个Handler)
enum QrResultCode {
  /// 页面路由
  route(1),
  /// webView 网页
  web(2),
  /// 不能解析的文本消息
  text(3),
  /// 无效code
  none(-1),
  ;
  final int code;

  const QrResultCode(this.code);


  void action(Map<String, dynamic> parameter, {void Function(Map<String, dynamic> parameter)? error}){
    switch (this) {
      case QrResultCode.route:
        var path = parameter['path'] as String;
        router.replace(path);
      default:
        error?.call(parameter);
    }
  }

  static QrResultCode valueOf(int? code){
    if(code==null){
      return QrResultCode.none;
    }
    for(var it in QrResultCode.values){
      if(it.code == code){
        return it;
      }
    }
    return QrResultCode.none;
  }

  IQrResult getHandler(Map<String, dynamic> jsonMap){
    switch(this){
      case route:
        return PageRouteQrResult.fromJson(jsonMap);
      default:
        return HttpWebQrResult.fromJson(jsonMap);
    }
  }

}